package com.xilihui.xlh.business.dialogs;


import android.app.Dialog;
import android.content.Context;
import android.util.DisplayMetrics;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.Window;
import android.view.WindowManager;


import com.xilihui.xlh.R;
import com.xilihui.xlh.component.view.LoopView;
import com.xilihui.xlh.core.util.LogUtil;
import com.xilihui.xlh.core.util.TimeFormatUtil;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

public class DatePickerDialog implements View.OnClickListener {

    private Context context;

    private List<String> yearList = new ArrayList<>();
    private List<String> monthList = new ArrayList<>();
    private List<String> dayList = new ArrayList<>();
    private int minYear = Calendar.getInstance().get(Calendar.YEAR);
    private int maxYear = Calendar.getInstance().get(Calendar.YEAR) + 50;
    private int minMonth = Calendar.getInstance().get(Calendar.MONTH) + 1;
    private int minDay = Calendar.getInstance().get(Calendar.DATE);

    private int currentYear;
    private int currentMonth;
    private int currentDay;

    private int yearPos = 0;
    private int monthPos = 0;
    private int dayPos = 0;

    private Dialog dialog;
    private Callback callback;

    /**
     * 日期选择(年月日)
     * 默认最小日期从今天开始，默认最大日期为今年+50年
     *
     * @param context
     */
    public DatePickerDialog(Context context) {

        this.context = context;
    }

    /**
     * 设置起始日期
     *
     * @param minYear
     * @param minMonth
     * @param minDay
     * @return
     */
    public DatePickerDialog setMinimalDate(int minYear, int minMonth, int minDay) {
        this.minYear = minYear;
        this.maxYear += 50;
        this.minMonth = minMonth;
        this.minDay = minDay;

        if (this.minYear <= 0) {
            throw new IllegalArgumentException("No such year [year = " + minYear + "]");
        }

        if (minMonth > 12 || minMonth <= 0) {
            throw new IllegalArgumentException("No such month [month = " + minMonth + "]");
        }
        return this;
    }

    public DatePickerDialog setCurrentDate(long mills) {
        String s = TimeFormatUtil.formatDate(mills);
        LogUtil.d("mylog","时间:"+s);
        String[] split = s.split("-");
        if(split.length>=3){
            this.currentYear = Integer.valueOf(split[0]);
            this.currentMonth = Integer.valueOf(split[1]);
            this.currentDay = Integer.valueOf(split[2]);

            if (this.currentYear <= 0) {
                throw new IllegalArgumentException("No such year [year = " + currentYear + "]");
            }

            if (currentMonth > 12 || currentMonth <= 0) {
                throw new IllegalArgumentException("No such month [month = " + currentMonth + "]");
            }

            if (currentDay <= 0) {
                throw new IllegalArgumentException("No such date [date = " + currentDay + "]");
            }
        }

        return this;
    }

    public DatePickerDialog setCurrentDate(int currentYear, int currentMonth, int currentDay) {
        this.currentYear = currentYear;
        this.currentMonth = currentMonth;
        this.currentDay = currentDay;

        if (this.currentYear <= 0) {
            throw new IllegalArgumentException("No such year [year = " + currentYear + "]");
        }

        if (currentMonth > 12 || currentMonth <= 0) {
            throw new IllegalArgumentException("No such month [month = " + currentMonth + "]");
        }

        if (currentDay <= 0) {
            throw new IllegalArgumentException("No such date [date = " + currentDay + "]");
        }

        return this;
    }

    /**
     * 设置最大可选年份
     *
     * @param maxYear
     */
    public DatePickerDialog setMaxYear(int maxYear) {

        if (maxYear < minYear) {
            throw new IllegalArgumentException("最大年份不能小于最小年份");
        }

        this.maxYear = maxYear;
        return this;
    }

    public DatePickerDialog setCallback(Callback callback) {

        this.callback = callback;
        return this;
    }

    public void show() {

        View view = LayoutInflater.from(context).inflate(R.layout.date_picker, null);

        view.findViewById(R.id.tvConfirm).setOnClickListener(this);
        view.findViewById(R.id.tvCancel).setOnClickListener(this);

        final LoopView picker_year = (LoopView) view.findViewById(R.id.picker_year);
        final LoopView picker_month = (LoopView) view.findViewById(R.id.picker_month);
        final LoopView picker_day = (LoopView) view.findViewById(R.id.picker_day);

        initYearPickerViews(picker_year, picker_month, picker_day);
        initMonthPickerViews(picker_month);
        initDayPickerView(picker_day);

        picker_year.setLoopListener(new LoopView.LoopScrollListener() {
            @Override
            public void onItemSelect(int index) {
                yearPos = index;
                initMonthPickerViews(picker_month);
                initDayPickerView(picker_day);
            }
        });

        picker_month.setLoopListener(new LoopView.LoopScrollListener() {
            @Override
            public void onItemSelect(int index) {
                monthPos = index;
                initDayPickerView(picker_day);
            }
        });

        picker_day.setLoopListener(new LoopView.LoopScrollListener() {
            @Override
            public void onItemSelect(int index) {
                dayPos = index;
            }
        });

        dialog = new Dialog(context, R.style.Dialog);
        dialog.setContentView(view);
        dialog.setCancelable(true);
        dialog.setCanceledOnTouchOutside(true);

        Window window = dialog.getWindow();
        if (window != null) {
            window.setGravity(Gravity.BOTTOM);
            WindowManager.LayoutParams lp = window.getAttributes();
            lp.width = getScreenWidth(context);
            lp.height = (int) (getScreenHeight(context) * 0.4);
            window.setAttributes(lp);
        }

        dialog.show();
    }

    private void initYearPickerViews(LoopView picker_year, LoopView picker_month, LoopView picker_day) {
        int yearCount = maxYear - minYear;
        yearList.clear();
        for (int i = 1; i <= yearCount; i++) {
            yearList.add(format2LenStr(minYear - 1 + i));
        }
        picker_year.setDataList(yearList);
        picker_year.setInitPosition(yearPos);

        for (int i = 0; i < yearList.size(); i++) {
            if (String.valueOf(currentYear).equals(yearList.get(i))) {
                picker_year.setInitPosition(i);
                yearPos = i;
                if (currentYear > minYear) {
                    initMonthPickerViews(picker_month);
                    initDayPickerView(picker_day);
                }
            }
        }
    }

    private void initMonthPickerViews(LoopView picker_month) {

        monthList.clear();

        if (yearPos == 0) {
            for (int j = minMonth; j <= 12; j++) {
                monthList.add(format2LenStr(j));
            }
        } else {
            for (int j = 1; j <= 12; j++) {
                monthList.add(format2LenStr(j));
            }
        }
        picker_month.setDataList(monthList);
        picker_month.setInitPosition(monthPos);

        for (int i = 0; i < monthList.size(); i++) {
            if (format2LenStr(currentMonth).equals(monthList.get(i))) {
                picker_month.setInitPosition(i);
                monthPos = i;
            }
        }
    }

    private void initDayPickerView(LoopView picker_day) {

        int dayMaxInMonth;
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.YEAR, minYear + yearPos);

        dayList.clear();
        if (yearPos == 0) {
            if (monthPos == 0) {
                // 得到当月最大天数
                calendar.set(Calendar.MONTH, minMonth - 1);
                dayMaxInMonth = calendar.getMaximum(Calendar.DAY_OF_MONTH);
                if (minDay > dayMaxInMonth || minDay <= 0) {
                    throw new IllegalArgumentException("No such date [date = " + minDay + "]");
                }
                for (int i = minDay; i <= dayMaxInMonth; i++) {
                    dayList.add(format2LenStr(i));
                }
            } else {
                calendar.set(Calendar.MONTH, minMonth + monthPos - 1);
                dayMaxInMonth = calendar.getMaximum(Calendar.DAY_OF_MONTH);
                if (minDay > dayMaxInMonth || minDay <= 0) {
                    throw new IllegalArgumentException("No such date [date = " + minDay + "]");
                }
                for (int i = 1; i <= dayMaxInMonth; i++) {
                    dayList.add(format2LenStr(i));
                }
            }
        } else {
            // 得到当月最大天数
            calendar.set(Calendar.MONTH, monthPos);
            dayMaxInMonth = calendar.getMaximum(Calendar.DAY_OF_MONTH);
            if (minDay > dayMaxInMonth || minDay <= 0) {
                throw new IllegalArgumentException("No such date [date = " + minDay + "]");
            }
            for (int i = 1; i <= dayMaxInMonth; i++) {
                dayList.add(format2LenStr(i));
            }
        }

        picker_day.setDataList(dayList);
        picker_day.setInitPosition(dayPos);

        if (currentDay > dayMaxInMonth) {
            throw new IllegalArgumentException("No such date [date = " + currentDay + "] in month " + currentMonth);
        }

        for (int i = 0; i < dayList.size(); i++) {
            if (format2LenStr(currentDay).equals(dayList.get(i))) {
                currentDay = -1;
                picker_day.setInitPosition(i);
                dayPos = i;
            }
        }
    }

    private String format2LenStr(int num) {
        return (num < 10) ? "0" + num : String.valueOf(num);
    }

    /**
     * 获得屏幕宽度
     *
     * @param context
     * @return
     */
    private int getScreenWidth(Context context) {
        WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
        DisplayMetrics outMetrics = new DisplayMetrics();
        wm.getDefaultDisplay().getMetrics(outMetrics);
        return outMetrics.widthPixels;
    }

    /**
     * 获得屏幕高度
     *
     * @param context
     * @return
     */
    private int getScreenHeight(Context context) {
        WindowManager wm = (WindowManager) context
                .getSystemService(Context.WINDOW_SERVICE);
        DisplayMetrics outMetrics = new DisplayMetrics();
        wm.getDefaultDisplay().getMetrics(outMetrics);
        return outMetrics.heightPixels;
    }

    @Override
    public void onClick(View v) {
        switch (v.getId()) {
            case R.id.tvConfirm:
                if (callback != null) {
                    if (yearPos == 0) {
                        if (monthPos == 0) {
                            callback.onSelected(minYear + yearPos, minMonth + monthPos, minDay + dayPos);
                        } else {
                            callback.onSelected(minYear + yearPos, minMonth + monthPos, dayPos + 1);
                        }
                    } else {
                        callback.onSelected(minYear + yearPos, monthPos + 1, dayPos + 1);
                    }
                }
                dialog.dismiss();
                break;
            case R.id.tvCancel:
                if (dialog != null) {
                    dialog.dismiss();
                }
                break;
        }
    }

    public interface Callback {
        void onSelected(int year, int month, int day);
    }
}
